package com.example.campus.dao.realm;

import com.example.campus.dao.model.shiro.Permission;
import com.example.campus.dao.table_gateway.shiro.PermissionMapper;
import com.example.campus.dao.table_gateway.shiro.RoleMapper;
import com.example.campus.dao.table_gateway.shiro.UserMapper;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.HashSet;


//@Component
public class MyAuthRealm extends AuthorizingRealm {

    @Autowired
    UserMapper userMapper;



    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
        var loginName = (String)token.getPrincipal();
        var user =  userMapper.getUserByLoginName(loginName);
        if(user == null){
            throw  new UnknownAccountException("User: " + loginName + " does not exists");
        }

        return new SimpleAuthenticationInfo(loginName, user.getPassword(),
                            /*realmName*/getName());
    }

    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        var loginName = (String)principalCollection.getPrimaryPrincipal();

        var accessInfo = new SimpleAuthorizationInfo();
        var roles = new HashSet<String>();
        var permUrls = new HashSet<String>();

        var user =  userMapper.getUserByLoginName(loginName);
        var uid = user.getId();

        user = userMapper.getUserWithRolesAndPermissions(uid);
        var perms = new HashSet<Permission>();
        user.getRoles().forEach((r)->{
            roles.add(r.getName());
            perms.addAll(r.getPermissions());
        });
        perms.forEach(p->{
            permUrls.add(p.getUrl());
        });

        accessInfo.setRoles(roles);
        accessInfo.setStringPermissions(permUrls);
        return accessInfo;
    }
}
